import {
  useDebounceFn,
  useGetState,
  useMemoizedFn,
  useMount,
  useSafeState,
} from "ahooks";
import { getValueOrDie } from "@common/utils";
import { useContext, useEffect, useMemo } from "react";
import { GlobalModel } from "@/ui/context";
import { BrowserSession, XHSMention } from "@common/models";
import * as xhsRPC from "@/ui/utils/rpc/xhs";
import { v4 as uuid } from "uuid";
import { omit } from "lodash-es";
import type { Props } from "./meta";
import { XHSComment } from "@common/models/xhs/notes";

export function useViewModel(props: Props) {
  const { commentReplyTo, onReplyToClick } = props;
  const [loading, setLoading] = useGetState(true);
  const globalModels = getValueOrDie(useContext(GlobalModel));
  const discussion = getValueOrDie(globalModels.discussion);
  const [myReplies, setMyReplies] = useSafeState<XHSComment[]>([]);

  const myRepliesInNote = useMemo(
    () => myReplies.filter((r) => r.note_id === discussion.note.noteId),
    [discussion.note.noteId, myReplies],
  );

  const records = useMemo(() => {
    let comments =
      globalModels.mentions?.records
        .filter((r) => r.item_info.id === discussion.note.noteId)
        .map((r: XHSMention) => {
          return {
            ...r.comment_info,
            user_info: {
              user_id: r.user_info.userid,
              xsec_token: "",
              nickname: r.user_info.nickname,
              image: r.user_info.image,
            },
            create_time: r.time * 1000,
            mention: r,
          } as Partial<XHSComment>;
        }) ?? [];
    comments = [...myRepliesInNote, ...comments];
    // @ts-expect-error  creat_time 必然存在
    comments.sort((a, b) => b.create_time - a!.create_time);
    return comments;
  }, [globalModels.mentions, discussion.note.noteId, myRepliesInNote]);

  const loadComments = useDebounceFn(async () => {}, {
    wait: 500,
    leading: true,
    trailing: false,
  });
  const loadSubComments = () => async () => {};

  const init = useDebounceFn(
    async () => {
      setLoading(true);
      const myReplies = await xhsRPC.getMyRepliesInNote({
        noteId: discussion.note.noteId,
      });
      setMyReplies(myReplies);
      setLoading(false);
    },
    { wait: 500, leading: true, trailing: false },
  );

  const post = useMemoizedFn(
    async (content: string, sendAsSession: BrowserSession) => {
      const sendTaskId = uuid();
      discussion.sendQueue.push(sendTaskId);
      const newComment = await xhsRPC.replyToCommentInNote({
        targetId: sendAsSession.apps.xhs.targetId,
        noteId: discussion.note.noteId,
        xsecToken: discussion.note.xsecToken,
        comment: commentReplyTo
          ? omit(
              commentReplyTo,
              "pictures",
              "sub_comment_count",
              "sub_comment_cursor",
              "sub_comment_has_more",
              "sub_comments",
              "target_comment",
            )
          : undefined,
        sessionId: sendAsSession.id,
        content,
      });
      console.log("new comment", newComment);

      // 插入到预期位置
      setMyReplies([newComment, ...myReplies]);
      discussion.sendQueue = discussion.sendQueue.filter(
        (r) => r !== sendTaskId,
      );

      if (onReplyToClick) {
        onReplyToClick(undefined);
      }
    },
  );

  useEffect(() => {
    const observer = new IntersectionObserver((entries) => {
      let changed = false;
      for (const e of entries) {
        if (e.intersectionRatio < 0.5) return;

        observer.unobserve(e.target);
        const commentId = (e.target as any).dataset["commentId"];
        const r = globalModels.mentions?.records.find(
          (r) => r.comment_info.id === commentId,
        );
        if (r && !r.isChecked) {
          r.isChecked = true;
          changed = true;
          xhsRPC.markMentionAsReaded({ id: r.id }).then();
        }
      }

      if (changed) {
        globalModels.mentions!.records = Array.from(
          globalModels.mentions!.records,
        );
      }
    });
    const tagsToObserve = Array.from(
      document.querySelectorAll(".message-card.unchecked"),
    );
    for (const tag of tagsToObserve) {
      observer.observe(tag);
    }
    return () => observer.disconnect();
  }, [records]);

  useMount(init.run);

  return {
    loading,
    globalModels,
    commentToReply: props.commentReplyTo,
    loadBtnId: "none",
    post,
    realSender: props.realSender,
    records,
    hasMore: false,

    loadComments,
    loadSubComments,
    setReplyTo: onReplyToClick,
  };
}
